from json import loads


def read_file(path, parse_func):
    num = -1
    with open(path, "r", encoding="utf8") as fin:
        line = fin.readline().strip()
        if line.isdigit():
            num = int(line.strip())
        else:
            fin.seek(0)
        lines = fin.readlines()

    lines = parse_func(lines)

    if len(lines) != num and num >= 0:
        raise ValueError()
    return lines


def read_mapping(path):
    def _parse(lines):
        for idx, line in enumerate(lines):
            name, i = line.strip().split('\t')
            lines[idx] = (name, int(i))
        return dict(lines)
    return read_file(path, _parse)

def read_triples(path):
    return read_file(path, lambda lines: [tuple([int(item) for item in line.strip().split('\t')]) for line in lines])

def read_rules(path, relation2id):
    def _parse(lines):
        lines = [loads(line) for line in lines]
        for i in range(len(lines)):
            premises, hypothesis, conf = lines[i]
            premises = tuple([(head, tail, relation2id[relation]) for head, tail, relation in premises])
            hypothesis = tuple([hypothesis[0], hypothesis[1], relation2id[hypothesis[2]]])
            conf = float(conf)
            lines[i] = (premises, hypothesis, conf)
        return lines
    return read_file(path, _parse)


import os, logging

def set_logger(args, log_name):
    '''
    Write logs to checkpoint and console
    '''
    if not os.path.exists(args.log_path):
        os.makedirs(args.log_path)


    log_file = os.path.join(args.log_path, '{}.log'.format(log_name))

    with open(log_file, "w", encoding="utf-8") as fout:
        fout.write("")

    logging.basicConfig(
        format='%(asctime)s %(levelname)-8s %(message)s',
        level=logging.INFO,
        datefmt='%Y-%m-%d %H:%M:%S',
        filename=log_file,
        filemode='a+'
    )
    console = logging.StreamHandler()
    console.setLevel(logging.INFO)
    formatter = logging.Formatter('%(asctime)s %(levelname)-8s %(message)s')
    console.setFormatter(formatter)
    logger = logging.getLogger('')
    logger.addHandler(console)
    return logger